/**
 * @file ctp_interface.cpp
 * @brief CTP交易接口实现
 * @details 实现了CTP行情和交易接口的核心功能
 */

#define _CRT_SECURE_NO_WARNINGS
#define _WINSOCK_DEPRECATED_NO_WARNINGS
#define _SILENCE_CXX17_CODECVT_HEADER_DEPRECATION_WARNING
#include <cstring>

#ifdef _WIN32
#pragma warning(disable: 4819)  // 禁用编码警告
#include "ctp/windows64/ThostFtdcUserApiDataType.h"
#include "ctp/windows64/ThostFtdcUserApiStruct.h"
#include "ctp/windows64/ThostFtdcMdApi.h"
#include "ctp/windows64/ThostFtdcTraderApi.h"
#else
#include "ctp/linux64/ThostFtdcUserApiDataType.h"
#include "ctp/linux64/ThostFtdcUserApiStruct.h"
#include "ctp/linux64/ThostFtdcMdApi.h"
#include "ctp/linux64/ThostFtdcTraderApi.h"
#endif

#include "market_data/ctp_interface.h"
#include "market_data/data_manager.h"
#include "core/performance_monitor.h"
#include <iostream>
#include <chrono>
#include <thread>
#include <memory>
#include <atomic>
#include <mutex>
#include <shared_mutex>
#include <map>
#include <spdlog/spdlog.h>

namespace hft {

/**
 * @brief CTP行情处理器构造函�?
 * @param config CTP配置信息
 */
CTPMarketDataHandler::CTPMarketDataHandler(const CTPConfig& config)
    : config_(config), connected_(false), api_(nullptr) {
    spi_ = std::make_unique<CTPMdSpi>(this);
}

/**
 * @brief CTP行情处理器析构函�?
 * @details 确保断开连接并释放资�?
 */
CTPMarketDataHandler::~CTPMarketDataHandler() {
    disconnect();
}

/**
 * @brief 连接CTP行情接口
 * @return 如果连接成功返回true，否则返回false
 * @details 创建CTP行情API实例并初始化连接
 */
bool CTPMarketDataHandler::connect() {
    try {
        // 检查是否已连接
        if (isConnected()) {
            spdlog::warn("CTP行情接口已连接，无需重复连接");
            return true;
        }

        // 创建CTP行情API实例
        api_ = CThostFtdcMdApi::CreateFtdcMdApi();
        if (!api_) {
            throw std::runtime_error("创建CTP行情API实例失败");
        }

        // 注册回调接口
        api_->RegisterSpi(spi_.get());

        // 注册前置机地址
        std::string front_addr = config_.front_addr;
        api_->RegisterFront(const_cast<char*>(front_addr.c_str()));
        
        // 初始化API
        api_->Init();
        
        // 等待连接成功，最多等待3秒
        const int max_retry = 30;
        for (int i = 0; i < max_retry && !connected_; ++i) {
            std::this_thread::sleep_for(std::chrono::milliseconds(100));
        }
        
        // 如果连接超时，释放资源
        if (!connected_) {
            api_->Release();
            api_ = nullptr;
            throw std::runtime_error(fmt::format(
                "CTP行情接口连接超时，前置机地址: {}", front_addr));
        }

        // 安全登录
        CThostFtdcReqUserLoginField req = {};
        auto safe_strncpy = [](char* dest, const std::string& src, size_t size) {
            size_t len = std::min(src.length(), size - 1);
            strncpy(dest, src.c_str(), len);
            dest[len] = '\0';
        };

        safe_strncpy(req.BrokerID, config_.broker_id, sizeof(req.BrokerID));
        safe_strncpy(req.UserID, config_.user_id, sizeof(req.UserID));
        safe_strncpy(req.Password, config_.password, sizeof(req.Password));
        
        int result = api_->ReqUserLogin(&req, 0);
        if (result != 0) {
            throw std::runtime_error(fmt::format(
                "CTP行情接口登录请求失败，错误码: {}", result));
        }
        
        // 启动心跳检测线程
        heartbeat_thread_ = std::thread([this]() {
            while (connected_) {
                std::this_thread::sleep_for(std::chrono::seconds(30));
                if (!checkHeartbeat()) {
                    spdlog::warn("CTP行情接口心跳检测失败");
                    disconnect();
                    std::this_thread::sleep_for(std::chrono::seconds(1));
                    connect(); // 自动重连
                }
            }
        });

        spdlog::info("CTP行情接口连接成功，前置机: {}", front_addr);
        return true;
    } catch (const std::exception& e) {
        // 发生异常时清理资�?
        if (api_) {
            api_->Release();
            api_ = nullptr;
        }
        spdlog::error("CTP行情接口连接失败: {}", e.what());
        return false;
    }
}

void CTPMarketDataHandler::onConnected() {
    connected_ = true;
}

void CTPMarketDataHandler::onDisconnected(int reason) {
    connected_ = false;
    spdlog::warn("CTP行情接口断开连接，原因：{}", reason);
}

void CTPMarketDataHandler::onLoginSuccess() {
    spdlog::info("CTP行情接口登录成功");
}

void CTPMarketDataHandler::onLoginFailed(int error_code, const std::string& error_msg) {
    spdlog::error("CTP行情接口登录失败：{} - {}", error_code, error_msg);
}

/**
 * @brief 断开CTP行情接口连接
 * @details 释放API资源并更新连接状�?
 */
void CTPMarketDataHandler::disconnect() {
    // 断开连接并释放资�?
    if (api_) {
        api_->Release();
        api_ = nullptr;
    }
    connected_ = false;
    spdlog::info("CTP行情接口已断开");
}

/**
 * @brief 检查CTP行情接口是否已连�?
 * @return 如果已连接返回true，否则返回false
 */
bool CTPMarketDataHandler::isConnected() const {
    return connected_ && api_ != nullptr;
}

/**
 * @brief 订阅行情
 * @param symbol 合约代码
 * @return 如果订阅成功返回true，否则返回false
 */
bool CTPMarketDataHandler::subscribe(const std::string& symbol) {
    if (!isConnected()) {
        return false;
    }
    
    try {
        // 使用智能指针管理内存，避免内存泄�?
        std::unique_ptr<char[]> instrument(new char[symbol.length() + 1]);
        strncpy(instrument.get(), symbol.c_str(), symbol.length());
        instrument[symbol.length()] = '\0';
        
        // 订阅行情
        char* instruments[] = {instrument.get()};
        int result = api_->SubscribeMarketData(instruments, 1);
        if (result != 0) {
            throw std::runtime_error("订阅行情失败: " + std::to_string(result));
        }
        
        spdlog::info("订阅行情: {}", symbol);
        return true;
    } catch (const std::exception& e) {
        spdlog::error("订阅行情失败: {}", e.what());
        return false;
    }
}

/**
 * @brief 取消订阅行情
 * @param symbol 合约代码
 * @return 如果取消订阅成功返回true，否则返回false
 */
bool CTPMarketDataHandler::unsubscribe(const std::string& symbol) {
    if (!isConnected()) {
        return false;
    }
    
    try {
        // 使用智能指针管理内存
        std::unique_ptr<char[]> instrument(new char[symbol.length() + 1]);
        strncpy(instrument.get(), symbol.c_str(), symbol.length());
        instrument[symbol.length()] = '\0';
        
        // 取消订阅行情
        char* instruments[] = {instrument.get()};
        int result = api_->UnSubscribeMarketData(instruments, 1);
        if (result != 0) {
            throw std::runtime_error("取消订阅行情失败: " + std::to_string(result));
        }
        
        spdlog::info("取消订阅行情: {}", symbol);
        return true;
    } catch (const std::exception& e) {
        spdlog::error("取消订阅行情失败: {}", e.what());
        return false;
    }
}

/**
 * @brief 获取最新行情数�?
 * @param symbol 合约代码
 * @return 最新行情数�?
 */
MarketDataMessage CTPMarketDataHandler::getLatestMarketData(const std::string& symbol) const {
    // 使用共享锁读取数据，允许多个线程同时读取
    std::shared_lock<std::shared_mutex> lock(data_mutex_);
    auto it = latest_data_.find(symbol);
    if (it != latest_data_.end()) {
        return it->second;
    }
    return MarketDataMessage();
}

/**
 * @brief 处理行情数据
 * @param msg 行情数据消息
 * @details 更新最新行情数据并通知数据管理�?
 */
void CTPMarketDataHandler::onMarketData(const MarketDataMessage& msg) {
    LatencyTimer timer("ctp_market_data");
    
    // 使用独占锁更新数据，确保数据一致�?
    std::unique_lock<std::shared_mutex> lock(data_mutex_);
    latest_data_[msg.symbol] = msg;
    
    // 将数据发送给数据管理�?
    DataManager::getInstance()->onTick(msg);
}

/**
 * @brief 处理错误信息
 * @param error_code 错误代码
 * @param error_msg 错误信息
 */
void CTPMarketDataHandler::onError(int error_code, const std::string& error_msg) {
    spdlog::error("CTP行情接口错误: {} - {}", error_code, error_msg);
}

/**
 * @brief CTP交易处理器构造函�?
 * @param config CTP配置信息
 */
CTPTraderHandler::CTPTraderHandler(const CTPConfig& config)
    : config_(config), connected_(false), api_(nullptr), request_id_(0) {
    spi_ = std::make_unique<CTPTraderSpi>(this);
}

/**
 * @brief CTP交易处理器析构函�?
 * @details 确保断开连接并释放资�?
 */
CTPTraderHandler::~CTPTraderHandler() {
    disconnect();
}

/**
 * @brief 连接CTP交易接口
 * @return 如果连接成功返回true，否则返回false
 * @details 创建CTP交易API实例并初始化连接
 */
bool CTPTraderHandler::connect() {
    try {
        // 检查是否已连接
        if (isConnected()) {
            spdlog::warn("CTP交易接口已连接，无需重复连接");
            return true;
        }

        // 创建CTP交易API实例
        api_ = CThostFtdcTraderApi::CreateFtdcTraderApi();
        if (!api_) {
            throw std::runtime_error("创建CTP交易API实例失败");
        }

        // 注册回调接口
        api_->RegisterSpi(spi_.get());

        // 注册前置机地址
        std::string front_addr = config_.front_addr;
        api_->RegisterFront(const_cast<char*>(front_addr.c_str()));
        
        // 初始化API
        api_->Init();
        
        // 等待连接成功，最多等待3秒
        const int max_retry = 30;
        for (int i = 0; i < max_retry && !connected_; ++i) {
            std::this_thread::sleep_for(std::chrono::milliseconds(100));
        }
        
        // 如果连接超时，释放资源
        if (!connected_) {
            api_->Release();
            api_ = nullptr;
            throw std::runtime_error(fmt::format(
                "CTP交易接口连接超时，前置机地址: {}", front_addr));
        }

        // 安全登录
        CThostFtdcReqUserLoginField req = {};
        auto safe_strncpy = [](char* dest, const std::string& src, size_t size) {
            size_t len = std::min(src.length(), size - 1);
            strncpy(dest, src.c_str(), len);
            dest[len] = '\0';
        };

        safe_strncpy(req.BrokerID, config_.broker_id, sizeof(req.BrokerID));
        safe_strncpy(req.UserID, config_.user_id, sizeof(req.UserID));
        safe_strncpy(req.Password, config_.password, sizeof(req.Password));
        safe_strncpy(req.AppID, config_.app_id, sizeof(req.AppID));
        safe_strncpy(req.AuthCode, config_.auth_code, sizeof(req.AuthCode));
        
        int result = api_->ReqUserLogin(&req, 0);
        if (result != 0) {
            throw std::runtime_error(fmt::format(
                "CTP交易接口登录请求失败，错误码: {}", result));
        }

        // 启动心跳检测线程
        heartbeat_thread_ = std::thread([this]() {
            while (connected_) {
                std::this_thread::sleep_for(std::chrono::seconds(30));
                if (!checkHeartbeat()) {
                    spdlog::warn("CTP交易接口心跳检测失败");
                    disconnect();
                    std::this_thread::sleep_for(std::chrono::seconds(1));
                    connect(); // 自动重连
                }
            }
        });

        // 查询结算信息确认
        CThostFtdcSettlementInfoConfirmField settle_conf = {};
        safe_strncpy(settle_conf.BrokerID, config_.broker_id, sizeof(settle_conf.BrokerID));
        safe_strncpy(settle_conf.InvestorID, config_.user_id, sizeof(settle_conf.InvestorID));
        api_->ReqSettlementInfoConfirm(&settle_conf, ++request_id_);

        spdlog::info("CTP交易接口连接成功，前置机: {}", front_addr);
        return true;
    } catch (const std::exception& e) {
        // 发生异常时清理资�?
        if (api_) {
            api_->Release();
            api_ = nullptr;
        }
        spdlog::error("CTP交易接口连接失败: {}", e.what());
        return false;
    }
}

void CTPTraderHandler::onConnected() {
    connected_ = true;
}

void CTPTraderHandler::onDisconnected(int reason) {
    connected_ = false;
    spdlog::warn("CTP交易接口断开连接，原因：{}", reason);
}

void CTPTraderHandler::onLoginSuccess() {
    spdlog::info("CTP交易接口登录成功");
}

void CTPTraderHandler::onLoginFailed(int error_code, const std::string& error_msg) {
    spdlog::error("CTP交易接口登录失败：{} - {}", error_code, error_msg);
}

/**
 * @brief 断开CTP交易接口连接
 * @details 释放API资源并更新连接状�?
 */
void CTPTraderHandler::disconnect() {
    // 断开连接并释放资�?
    if (api_) {
        api_->Release();
        api_ = nullptr;
    }
    connected_ = false;
    spdlog::info("CTP交易接口已断开");
}

/**
 * @brief 检查CTP交易接口是否已连�?
 * @return 如果已连接返回true，否则返回false
 */
bool CTPTraderHandler::isConnected() const {
    return connected_ && api_ != nullptr;
}

/**
 * @brief 提交订单
 * @param order 订单信息
 * @return 如果提交成功返回true，否则返回false
 * @details 将订单转换为CTP订单格式并提�?
 */
bool CTPTraderHandler::submitOrder(const Order& order) {
    LatencyTimer timer("ctp_order_submission");
    
    if (!isConnected()) {
        return false;
    }
    
    try {
        // 构建CTP订单结构
        CThostFtdcInputOrderField input_order = {};
        strncpy(input_order.BrokerID, config_.broker_id.c_str(), sizeof(input_order.BrokerID) - 1);
        strncpy(input_order.InvestorID, config_.user_id.c_str(), sizeof(input_order.InvestorID) - 1);
        strncpy(input_order.InstrumentID, order.symbol.c_str(), sizeof(input_order.InstrumentID) - 1);
        strncpy(input_order.OrderRef, order.order_id.c_str(), sizeof(input_order.OrderRef) - 1);
        input_order.OrderPriceType = THOST_FTDC_OPT_LimitPrice;  // 限价�?
        input_order.Direction = order.side == OrderSide::BUY ? THOST_FTDC_D_Buy : THOST_FTDC_D_Sell;
        input_order.CombOffsetFlag[0] = THOST_FTDC_OF_Open;  // 开�?
        input_order.CombHedgeFlag[0] = THOST_FTDC_HF_Speculation;  // 投机
        input_order.LimitPrice = order.price;
        input_order.VolumeTotalOriginal = order.quantity;
        input_order.TimeCondition = THOST_FTDC_TC_GFD;  // 当日有效
        input_order.VolumeCondition = THOST_FTDC_VC_AV;  // 任意数量
        input_order.ContingentCondition = THOST_FTDC_CC_Immediately;  // 立即
        input_order.ForceCloseReason = THOST_FTDC_FCC_NotForceClose;
        input_order.IsAutoSuspend = 0;
        input_order.UserForceClose = 0;
        
        // 提交订单
        int result = api_->ReqOrderInsert(&input_order, ++request_id_);
        if (result != 0) {
            throw std::runtime_error("提交订单失败: " + std::to_string(result));
        }
        
        spdlog::info("提交订单: {} 价格: {} 数量: {}", order.symbol, order.price, order.quantity);
        return true;
    } catch (const std::exception& e) {
        spdlog::error("提交订单失败: {}", e.what());
        return false;
    }
}

/**
 * @brief 取消订单
 * @param order_id 订单ID
 * @return 如果取消成功返回true，否则返回false
 */
bool CTPTraderHandler::cancelOrder(const std::string& order_id) {
    if (!isConnected()) {
        return false;
    }
    
    try {
        // 构建CTP撤单结构
        CThostFtdcInputOrderActionField action = {};
        strncpy(action.BrokerID, config_.broker_id.c_str(), sizeof(action.BrokerID) - 1);
        strncpy(action.InvestorID, config_.user_id.c_str(), sizeof(action.InvestorID) - 1);
        strncpy(action.OrderRef, order_id.c_str(), sizeof(action.OrderRef) - 1);
        action.ActionFlag = THOST_FTDC_AF_Delete;
        
        // 提交撤单请求
        int result = api_->ReqOrderAction(&action, ++request_id_);
        if (result != 0) {
            throw std::runtime_error("取消订单失败: " + std::to_string(result));
        }
        
        spdlog::info("取消订单: {}", order_id);
        return true;
    } catch (const std::exception& e) {
        spdlog::error("取消订单失败: {}", e.what());
        return false;
    }
}

/**
 * @brief 获取订单状�?
 * @param order_id 订单ID
 * @return 订单状�?
 */
OrderStatus CTPTraderHandler::getOrderStatus(const std::string& order_id) {
    std::shared_lock<std::shared_mutex> lock(order_mutex_);
    auto it = order_status_.find(order_id);
    if (it != order_status_.end()) {
        return it->second;
    }
    return OrderStatus::REJECTED;
}

/**
 * @brief 处理订单回报
 * @param order 订单信息
 * @details 更新订单状态并通知相关组件
 */
void CTPTraderHandler::onOrder(const Order& order) {
    std::unique_lock<std::shared_mutex> lock(order_mutex_);
    order_status_[order.order_id] = order.status;
    
    // 通知订单管理�?
    if (order_manager_) {
        order_manager_->onOrderUpdate(order);
    }
}

/**
 * @brief 处理成交回报
 * @param trade 成交信息
 * @details 更新订单状态并通知相关组件
 */
void CTPTraderHandler::onTrade(const Trade& trade) {
    std::unique_lock<std::shared_mutex> lock(order_mutex_);
    
    // 更新订单状�?
    auto it = order_status_.find(trade.order_id);
    if (it != order_status_.end()) {
        it->second = OrderStatus::FILLED;
    }
    
    // 通知订单管理�?
    if (order_manager_) {
        Order order;
        order.order_id = trade.order_id;
        order.symbol = trade.symbol;
        order.price = trade.price;
        order.quantity = trade.quantity;
        order.status = OrderStatus::FILLED;
        order_manager_->onOrderUpdate(order);
    }
}

/**
 * @brief 处理错误信息
 * @param error_code 错误代码
 * @param error_msg 错误信息
 */
void CTPTraderHandler::onError(int error_code, const std::string& error_msg) {
    std::lock_guard<std::mutex> lock(error_mutex_);
    spdlog::error("CTP交易接口错误: {} - {}", error_code, error_msg);
}

// CTP接口类实�?
CTPInterface::CTPInterface(const CTPConfig& config)
    : config_(config) {
}

CTPInterface::~CTPInterface() {
    cleanup();
}

bool CTPInterface::initialize() {
    try {
        // 创建并初始化行情处理�?
        market_data_handler_ = std::make_shared<CTPMarketDataHandler>(config_);
        if (!market_data_handler_->connect()) {
            return false;
        }
        
        // 创建并初始化交易处理�?
        trader_handler_ = std::make_shared<CTPTraderHandler>(config_);
        if (!trader_handler_->connect()) {
            market_data_handler_->disconnect();
            return false;
        }
        
        return true;
    } catch (const std::exception& e) {
        last_error_ = e.what();
        return false;
    }
}

void CTPInterface::cleanup() {
    // 清理资源，断开连接
    if (trader_handler_) {
        trader_handler_->disconnect();
    }
    if (market_data_handler_) {
        market_data_handler_->disconnect();
    }
}

std::shared_ptr<CTPMarketDataHandler> CTPInterface::getMarketDataHandler() const {
    return market_data_handler_;
}

std::shared_ptr<CTPTraderHandler> CTPInterface::getTraderHandler() const {
    return trader_handler_;
}

bool CTPInterface::isConnected() const {
    return market_data_handler_ && market_data_handler_->isConnected() &&
           trader_handler_ && trader_handler_->isConnected();
}

std::string CTPInterface::getLastError() const {
    std::lock_guard<std::mutex> lock(error_mutex_);
    return last_error_;
}

} // namespace hft 